home *** CD-ROM | disk | FTP | other *** search
/ Power Programmierung 2 / Power-Programmierung CD 2 (Tewi)(1994).iso / gnu / gnulib / sipp / sphigs / include / mat3.h < prev    next >
Encoding:
C/C++ Source or Header  |  1994-02-16  |  14.9 KB  |  436 lines

  1. /* Copyright 1991, Brown Computer Graphics Group.  All Rights Reserved. */
  2.  
  3. /* -------------------------------------------------------------------------
  4.                Public MAT3 include file
  5.    ------------------------------------------------------------------------- */
  6.  
  7. /* $Id: mat3.h,v 1.4 1993/03/09 02:00:54 crb Exp $ */
  8.  
  9. #ifndef MAT3_HAS_BEEN_INCLUDED
  10. #define MAT3_HAS_BEEN_INCLUDED
  11.  
  12. /* -----------------------------  Constants  ------------------------------ */
  13.  
  14. /*
  15.  * Make sure the math library .h file is included, in case it wasn't.
  16.  */
  17.  
  18. #ifndef HUGE
  19. #include <math.h>
  20. #define HUGE_VAL HUGE
  21. #endif
  22. #include <stdio.h>
  23. #include <stdlib.h>
  24. #include <string.h>
  25.  
  26. #ifdef lint
  27. #define MAT3_FIX  , errno = 1
  28. #else
  29. #define MAT3_FIX
  30. #endif
  31.  
  32. #define MAT3_EPSILON    1e-12            /* Close enough to zero   */
  33. #define MAT3_PI     M_PI            /* Pi              */
  34. #define MAT3_NULL_MAT    MAT3_null_mat
  35.  
  36. /*
  37.  * DESCR :    Determines how many values we store in our precomputed
  38.  *           sin and cos tables
  39.  */
  40. #define MAT3_SIN_RES    360
  41.  
  42. #define MAT3__MAT_REF(MMAT)  ((MMAT)->ref)
  43. #define MAT3__VEC_REF(MVEC)  ((MVEC)->ref)
  44. #define MAT3__MAT_MAT(MMAT)  ((MMAT)->mat)
  45. #define MAT3__VEC_VEC(MVEC)  ((MVEC)->vec)
  46.  
  47. /* ------------------------------  Types  --------------------------------- */
  48.  
  49. #define BOOL unsigned char
  50.  
  51. typedef double MAT3mat[4][4];        /* 4x4 matrix             */
  52. typedef double MAT3vec[3];        /* Vector             */
  53. typedef double MAT3hvec[4];             /* Vector with homogeneous coord */
  54.  
  55. /* ------------------------------  Macros  -------------------------------- */
  56.  
  57. /*
  58.  * TITLE   :    Comparison macros
  59.  * RETURNS :    int
  60.  */
  61.  
  62. /* 
  63.  * DESCR   :    Tests if a number is within EPSILON of zero
  64.  */
  65. #define MAT3_IS_ZERO(N)     ((N) < MAT3_EPSILON && (N) > -MAT3_EPSILON)
  66.  
  67. /* 
  68.  * DESCR   :    Tests a vector @V@ for all components being close to zero
  69.  */
  70. #define MAT3_IS_ZERO_VEC(V)    (MAT3_IS_ZERO((V)[0]) && \
  71.                  MAT3_IS_ZERO((V)[1]) && \
  72.                  MAT3_IS_ZERO((V)[2]))
  73.  
  74. /* 
  75.  * DESCR   :    Tests if two numbers @A@ and @B@ are within EPSILON of each 
  76.  *             other.
  77.  */
  78. #define MAT3__EQ(A,B)                    \
  79.     ((A) < (B) ? (((B) - (A)) < MAT3_EPSILON) :     \
  80.              (((A) - (B)) < MAT3_EPSILON))
  81.  
  82. /*
  83.  * DESCR   :    Tests if vectors @V1@ and @V2@ are within EPSILON of each other.
  84.  */
  85. #define MAT3_EQUAL_VECS(V1, V2)                        \
  86.     (MAT3__EQ((V1)[0], (V2)[0]) && MAT3__EQ((V1)[1], (V2)[1]) &&    \
  87.      MAT3__EQ((V1)[2], (V2)[2]))
  88.  
  89. /*
  90.  * TITLE   :    Vector operations
  91.  * RETURNS :    void
  92.  */
  93.  
  94. #define MAT3_SET_VEC(RESULT_V,X,Y,Z)    \
  95.         ((RESULT_V)[0]=(X), (RESULT_V)[1]=(Y), (RESULT_V)[2]=(Z) MAT3_FIX)
  96. #define MAT3_COPY_VEC(TO,FROM)    ((TO)[0] = (FROM)[0], \
  97.                  (TO)[1] = (FROM)[1], \
  98.                  (TO)[2] = (FROM)[2] MAT3_FIX)
  99.  
  100. /*
  101.  * TITLE   :
  102.  * DESCR   :    Basic operations on vector @V@, that modify vector
  103.  *        @RESULT_V@.
  104.  *
  105.  */
  106.  
  107. #define MAT3_NEGATE_VEC(RESULT_V,V) \
  108.         MAT3_SET_VEC(RESULT_V, -(V)[0], -(V)[1], -(V)[2])
  109.  
  110. #define MAT3_SCALE_VEC(RESULT_V,V,SCALE) \
  111.     MAT3_SET_VEC(RESULT_V, (V)[0]*(SCALE), (V)[1]*(SCALE), (V)[2]*(SCALE))
  112.  
  113.  
  114. #define MAT3_ADD_VEC(RESULT_V,V1,V2) \
  115.     MAT3_SET_VEC(RESULT_V, (V1)[0]+(V2)[0], (V1)[1]+(V2)[1], \
  116.                    (V1)[2]+(V2)[2])
  117.  
  118. #define MAT3_SUB_VEC(RESULT_V,V1,V2) \
  119.     MAT3_SET_VEC(RESULT_V, (V1)[0]-(V2)[0], (V1)[1]-(V2)[1], \
  120.                    (V1)[2]-(V2)[2])
  121.  
  122. #define MAT3_MULT_VEC(RESULT_V,V1,V2) \
  123.     MAT3_SET_VEC(RESULT_V, (V1)[0]*(V2)[0], (V1)[1]*(V2)[1], \
  124.                    (V1)[2]*(V2)[2])
  125.  
  126. /*
  127.  * TITLE   :
  128.  * DESCR   :    More  complex operations on multiple vectors
  129.  *
  130.  */
  131.  
  132. /*
  133.  * DESCR   :    Compute dot product of 3-vectors @V1@ and @V2@
  134.  * RETURNS :    double
  135.  */
  136. #define MAT3_DOT_PRODUCT(V1,V2) \
  137.             ((V1)[0]*(V2)[0] + (V1)[1]*(V2)[1] + (V1)[2]*(V2)[2])
  138.  
  139. /*
  140.  * DESCR   :    Compute length of 3-vector @V@.
  141.  * RETURNS :    double
  142.  */
  143. #define MAT3_LENGTH_VEC(V)    (sqrt(MAT3_DOT_PRODUCT(V, V)))
  144.  
  145. /*
  146.  * DESCR :    Place the cross product of @VEC1@ and @VEC2@ in @RESULT_VEC@.
  147.  *         @TEMP@ is used to hold an intermediate result.
  148.  * DETAILS :    The factors and the product vectors may safely be the same.
  149.  */
  150. #define MAT3_CROSS_PRODUCT(RESULT_VEC, VEC1, VEC2, TEMP)             \
  151.        ((TEMP)[0] = (VEC1)[1] * (VEC2)[2] - (VEC1)[2] * (VEC2)[1],   \
  152.         (TEMP)[1] = (VEC1)[2] * (VEC2)[0] - (VEC1)[0] * (VEC2)[2],   \
  153.         (TEMP)[2] = (VEC1)[0] * (VEC2)[1] - (VEC1)[1] * (VEC2)[0],   \
  154.         MAT3_COPY_VEC(RESULT_VEC, TEMP))
  155.  
  156. /*
  157.  * DESCR :    Place the cross product of @VEC1@ and @VEC2@ in @RVEC@.
  158.  *         The arguments must not be the same as the result vector.
  159.  * DETAILS :    The result cannot be the same as the factor vectors.
  160.  */
  161. #define MAT3_CROSS_PRODUCT_QUICK(RVEC, VEC1, VEC2)                  \
  162.        ((RVEC)[0] = (VEC1)[1] * (VEC2)[2] - (VEC1)[2] * (VEC2)[1],  \
  163.         (RVEC)[1] = (VEC1)[2] * (VEC2)[0] - (VEC1)[0] * (VEC2)[2],  \
  164.         (RVEC)[2] = (VEC1)[0] * (VEC2)[1] - (VEC1)[1] * (VEC2)[0]  MAT3_FIX)
  165.  
  166.  
  167. /*
  168.  * DESCR   :    Normalize the 3-vector @V@, using @TEMP@ as temporary variable.
  169.  * DETAILS :    If the norm of @V@ is too close to zero, no normalization
  170.  *         takes place, and @TEMP@ is set to zero.
  171.  */
  172. #define MAT3_NORMALIZE_VEC(V,TEMP) \
  173.     if ((TEMP = sqrt(MAT3_DOT_PRODUCT(V,V))) > MAT3_EPSILON) { \
  174.        TEMP = 1.0 / TEMP; \
  175.        MAT3_SCALE_VEC(V,V,TEMP); \
  176.     } else TEMP = 0.0
  177.  
  178. /*
  179.  * DESCR   :    Sets @RESULT_V@ to the linear combination of @V1@ and @V2@,
  180.  *         scaled by @SCALE1@ and @SCALE2@, respectively 
  181.  */
  182. #define MAT3_LINEAR_COMB(RESULT_V,SCALE1,V1,SCALE2,V2) \
  183.     MAT3_SET_VEC(RESULT_V,    (SCALE1)*(V1)[0] + (SCALE2)*(V2)[0], \
  184.                 (SCALE1)*(V1)[1] + (SCALE2)*(V2)[1], \
  185.                 (SCALE1)*(V1)[2] + (SCALE2)*(V2)[2])
  186.  
  187. /*
  188.  * DESCR   :    Set @RESULT_V@ to be @V1@ + @SCALE2@ * @V2@.
  189.  */
  190. #define MAT3_RAY_POINT(RESULT_V,V1,SCALE2,V2) \
  191.     MAT3_SET_VEC(RESULT_V,    (V1)[0] + (SCALE2)*(V2)[0], \
  192.                 (V1)[1] + (SCALE2)*(V2)[1], \
  193.                 (V1)[2] + (SCALE2)*(V2)[2])
  194.  
  195. /*
  196.  * DESCR   :    The point @POINT@ and the plane-through-the-origin given by
  197.  *         the equation @NORMAL@ dot (X, Y, Z) = 0 together can be used
  198.  *         to determine a basis for 3-space. The second vector in the
  199.  *         basis is the plane normal @NORMAL@. The first is some vector
  200.  *         perpendicular to this, i.e., some vector in the plane. The
  201.  *         third vector in the basis is the cross product of these two.
  202.  *         These vectors are placed in the first three rows of the 4
  203.  *         x 4 matrix @BASIS@, and the last row gets the given point
  204.  *         @POINT@ put in it.
  205.  */
  206. #define MAT3_BASIS_FROM_PLANE(BASIS, POINT, NORMAL)                    \
  207.         ((BASIS)[0][3]=(BASIS)[1][3]=(BASIS)[2][3]=0, (BASIS)[3][3]=1, \
  208.          MAT3_COPY_VEC((BASIS)[3], POINT),                             \
  209.          MAT3_COPY_VEC((BASIS)[1], NORMAL),                            \
  210.          MAT3perp_vec ((BASIS)[0], NORMAL, TRUE),                      \
  211.          MAT3_CROSS_PRODUCT_QUICK((BASIS)[2], NORMAL, (BASIS)[0]))
  212.  
  213. /*
  214.  * TITLE   :    Homogeneous vector operations
  215.  */
  216.  
  217. #define MAT3_SET_HVEC(V,X,Y,Z,W) ((V)[0]=(X), (V)[1]=(Y), \
  218.                   (V)[2]=(Z), (V)[3]=(W) MAT3_FIX)
  219.  
  220. #define MAT3_COPY_HVEC(TO,FROM) ((TO)[0] = (FROM)[0], \
  221.                  (TO)[1] = (FROM)[1], \
  222.                  (TO)[2] = (FROM)[2], \
  223.                  (TO)[3] = (FROM)[3] MAT3_FIX)
  224.  
  225. /*
  226.  * TITLE   :
  227.  * DESCR   :    Basic operations on homogeneous vectors
  228.  *
  229.  */
  230. #define MAT3_ADD_HVEC(RESULT_V,V1,V2)                     \
  231.     MAT3_SET_HVEC(RESULT_V, (V1)[0]+(V2)[0], (V1)[1]+(V2)[1],     \
  232.                    (V1)[2]+(V2)[2], (V1)[3]+(V2)[3] )
  233.  
  234. #define MAT3_SCALE_HVEC(RESULT_V,V,SCALE)                \
  235.     MAT3_SET_HVEC(RESULT_V, (V)[0]*(SCALE), (V)[1]*(SCALE),     \
  236.              (V)[2]*(SCALE), (V)[3]*(SCALE))
  237.  
  238. /*
  239.  * TITLE   :    Fast math
  240.  * DESCR   :    Compute sin or cos of @X@ (an angle in radians) by table lookup
  241.  *         Returns the approximate value of the trig function. @X@ is in
  242.  *        degrees in the second two macros.
  243.  *
  244.  * RETURNS :    double
  245.  */
  246. #define MAT3_FAST_SIN(X)   (MAT3_sin[(int)(180.0*(X)/M_PI) % 360]) /* X is in */
  247. #define MAT3_FAST_COS(X)   (MAT3_cos[(int)(180.0*(X)/M_PI) % 360]) /* radians */
  248. #define MAT3_FAST_SIN_DEG(X) (MAT3_sin[((int) (X)) % 360]) /* X is in  */
  249. #define MAT3_FAST_COS_DEG(X) (MAT3_cos[((int) (X)) % 360]) /* degrees  */
  250.  
  251. /* ------------------------------  Entries  ------------------------------- */
  252.  
  253. /* In MAT3factor.c */
  254.  
  255. BOOL MAT3factor(
  256.          MAT3mat m,            /* Source matrix to be factored  */
  257.          MAT3mat r,            /* Rotation for conjugation  */
  258.          MAT3mat s,            /* Scale in rotated coord system  */ 
  259.          MAT3mat u,            /* Rotation of conjugated matrix  */
  260.          MAT3mat t            /* Translation component  */
  261. );
  262. BOOL MAT3eigen_values(
  263.          MAT3vec values,         /* Eigenvalues of the second argument */
  264.          MAT3mat mat             /* Matrix of interest */
  265. );
  266.  
  267.  
  268. /* In MAT3geom.c */
  269.  
  270. void MAT3direction_matrix(
  271.          register MAT3mat result_mat,    /* Matrix for transforming directions */
  272.          register MAT3mat mat         /* Source matrix */
  273. );
  274. int MAT3normal_matrix(
  275.          register MAT3mat result_mat,    /* The compute normal matrix */
  276.          register MAT3mat mat         /* Matrix from which it is computed */
  277. );
  278. void MAT3scale(
  279.          MAT3mat result_mat,        /* Scale matrix [output] */
  280.          MAT3vec scale             /* The entries for the diagonal */
  281. );
  282. void MAT3rotate(
  283.          MAT3mat result_mat,        /* Rotation matrix [output] */
  284.          MAT3vec axis,            /* The axis of the rotation matrix */
  285.          double    angle_in_radians    /* The angle of rotation */
  286. );
  287. void MAT3translate(
  288.          MAT3mat result_mat,        /* Translation matrix [output] */
  289.          MAT3vec trans            /* Translation vector [input]  */
  290. );
  291. void MAT3mirror(
  292.          MAT3mat result_mat,        /* Matrix reflected through plane */
  293.          MAT3vec normal         /* Plane normal to plane thru origin */
  294. );
  295. void MAT3shear(
  296.          register MAT3mat result_mat,    /* Shear matrix [output] */
  297.          register MAT3vec normal,    /* Normal to the shear plane */
  298.          register MAT3vec shear     /* Shearing vector [perp to normal] */
  299. );
  300. int MAT3orient(
  301.          MAT3mat result_mat,        /* Orientation matrix [output] */
  302.          MAT3vec from,            /* Pt to which origin is translated */
  303.          MAT3vec at,            /* Z-axis is transformed to from-at */
  304.          MAT3vec up             /* Y-axis is transformed to from-up */
  305. );
  306. int MAT3span(
  307.          MAT3mat   result_mat,        /* Span xform matrix [output] */
  308.          MAT3vec   from,        /* Where the -1 point on Z-axis goes */
  309.          MAT3vec   at,            /* Where the +1 point on Z-axis goes */
  310.          MAT3vec   up,            /* Where the Y-axis goes */
  311.          int       vol_preserve     /* Should we preserve volume?  */
  312. );
  313. int MAT3axis_and_angle(
  314.          register MAT3mat mat,        /* A rotation matrix to be studied */
  315.          MAT3vec       axis,        /* The axis of rotation */
  316.          double          *angle     /* The amount of the rotation */
  317. );
  318. void MAT3align(
  319.          MAT3mat result_mat,    /* Computed matrix aligning vec1 with vec2 */
  320.          MAT3vec vec1,    /* Vector to be transformed */
  321.          MAT3vec vec2     /* We want to move vec1 so that it points same */
  322.          /* dir'n as vec2 */);
  323.  
  324.  
  325. /* In MAT3inv.c */
  326.  
  327. int MAT3invert(
  328.          MAT3mat result_mat,        /* The computed inverse */
  329.          MAT3mat mat             /* The matrix to be inverted */);
  330.  
  331.  
  332. /* In MAT3mat.c */
  333.  
  334. void MAT3identity(
  335.          MAT3mat m             /* Matrix to be set to identity */
  336. );
  337. void MAT3zero(
  338.          MAT3mat m             /* Matrix to be set to zero */
  339. );
  340. double MAT3determinant(
  341.          MAT3mat mat             /* Matrix of interest */
  342. );
  343. void MAT3copy(
  344.          MAT3mat t,            /* Target matrix [output] */
  345.          MAT3mat f            /* Source matrix [input] */
  346. );
  347. void MAT3mult(
  348.          MAT3mat result_mat,        /* Computed product [output] */
  349.          MAT3mat mat1,            /* The first factor of the product */
  350.          MAT3mat mat2             /* The second factor of the product */
  351. );
  352. void MAT3transpose(
  353.          MAT3mat result_mat,        /* The computed transpose */
  354.          MAT3mat mat             /* Matrix whose transpose we compute */
  355. );
  356. void MAT3print(
  357.          MAT3mat mat,            /* The matrix to be printed */
  358.          FILE    *fp             /* The stream on which to print it */
  359. );
  360. void MAT3print_formatted(
  361.          MAT3mat mat,            /* Matrix to be printed out */
  362.          FILE    *fp,            /* File stream to which it is printed */
  363.          char    *title,            /* Title of printout */
  364.          char    *head,            /* Printed before each row of matrix */
  365.          char    *format,        /* Format for entries of matrix */
  366.          char    *tail             /* Printed after each row of matrix */
  367. );
  368. BOOL MAT3equal(
  369.          MAT3mat m1,            /* First matrix to be compared */
  370.          MAT3mat m2,            /* Second matrix to be compared */
  371.          double    epsilon         /* Range for a match */
  372. );
  373. double MAT3trace(
  374.          MAT3mat mat            /* Matrix to compute trace for */
  375. );
  376. int MAT3power(
  377.          MAT3mat result_mat,        /* Source matrix raised to the power */
  378.          MAT3mat mat,            /* Source matrix */
  379.          int    power             /* Power to raise by */
  380. );
  381. int MAT3column_reduce(
  382.          MAT3mat result_mat,        /* Column-reduced matrix [output] */
  383.          MAT3mat mat,            /* Original matrix [input] */
  384.          double     epsilon         /* Tolerance for testing against 0 */
  385. );
  386. int MAT3kernel_basis(
  387.          MAT3mat result_mat,        /* Basis of kernel of matx [output] */
  388.          MAT3mat      mat,        /* Matrix whose kernel we compute */
  389.          double     epsilon         /* Tolerance for comparison with zero */
  390. );
  391. void MAT3scalar_mult(
  392.          MAT3mat result_mat,        /* Result of scale [output] */
  393.          MAT3mat m,            /* Matrix to be scaled [input] */
  394.          double  scalar         /* Scaling factor [input] */
  395. );
  396. void MAT3mat_add(
  397.          MAT3mat result_mat,        /* The sum of the matrices [output] */
  398.          MAT3mat A,            /* The first summand [input] */
  399.          MAT3mat B             /* The second summand [input] */
  400. );
  401.  
  402.  
  403. /* In MAT3vec.c */
  404.  
  405. /* The ordering of "vec" and "mat" parameters in following three functions is
  406.  * probably counterintuitive but is retained for backward compatibility.
  407.  */
  408. void MAT3mult_vec(
  409.          register MAT3vec result_vec,    /* Product of vec and mat (output) */
  410.          register MAT3vec vec,        /* Vec to be multiplied (input) */
  411.          register MAT3mat mat         /* Matrix it's multiplied by (input)*/
  412. );
  413. int MAT3mult_hvec(
  414.          MAT3hvec          result_vec,    /* Product of vec with mat (output) */
  415.          register MAT3hvec vec,        /* Vector to multiply (input) */
  416.          register MAT3mat  mat,        /* Matrix to multiply (input) */
  417.          int               homogenize    /* Should we homogenize the result? */
  418. );
  419. int MAT3mult_vec_affine(
  420.          MAT3vec           result_vec,    /* The computed product (output) */
  421.          register MAT3vec  vec,        /* The vector factor (input) */
  422.          register MAT3mat  mat        /* The matrix factor (input) */
  423. );
  424. void MAT3cross_product(
  425.          MAT3vec      result_vec,    /* Computed cross-product (output) */
  426.          register MAT3vec vec1,        /* The first factor (input) */
  427.          register MAT3vec vec2         /* The second factor (input) */
  428. );
  429. void MAT3perp_vec(
  430.          MAT3vec result_vec,        /* The vector perp to vec (output) */
  431.          MAT3vec vec,            /* Vector to which a perp is needed */
  432.          int is_unit             /* Is input vector is a unit vector? */
  433. );
  434.  
  435. #endif /* MAT3_HAS_BEEN_INCLUDED */
  436.